package edu.tec.mty.extras.fuzzy;

//Class for fuzzy rules Specifically created for Phoenix
public class FuzzyRule {
	//Input initializes as null for error detection
		public InputGaussMF Input1 = null;
		public InputGaussMF Input2 = null;
		public InputGaussMF Input3 = null;
		public InputGaussMF Input4 = null;
		public InputGaussMF Input5 = null;
		
		public OutputGaussMF Output1 = null;
		public OutputGaussMF Output2 = null;
		public OutputGaussMF Output3 = null;
		//The default junction will be and
		public String andOrIn = "and";
		public String andOrOut = "and";
		
		public String outMessage;
		
		public FuzzyRule(String andorin, InputGaussMF i1, InputGaussMF i2, 
				InputGaussMF i3, InputGaussMF i4, InputGaussMF i5, String andorout, OutputGaussMF out1, 
				OutputGaussMF out2, OutputGaussMF out3){

			Input1 = i1;
			Input2 = i2;
			Input3 = i3;
			Input4 = i4;
			Input5 = i5;
			Output1 = out1;
			Output2 = out2;
			Output3 = out3;
			andOrIn = andorin;
			andOrOut = andorout;
		}
		
		public FuzzyRule(String andorin, InputGaussMF i1, InputGaussMF i2, 
				         String andorout, OutputGaussMF out1,OutputGaussMF out2, OutputGaussMF out3){

			Input1 = i1;
			Input2 = i2;
			Input3 = null;
			Input4 = null;
			Input5 = null;
			Output1 = out1;
			Output2 = out2;
			Output3 = out3;
			andOrIn = andorin;
			andOrOut = andorout;
		}
		
		//Writes the defined rule
		public String publicate(){
			String outMessage;
			if((Input3 == null)||(Input4 == null)||(Input5 == null)){
					outMessage = "If " + Input1.publicate() + " " + andOrIn + " " + Input2.publicate() + " " 
						+ andOrIn + " " + Input3.publicate() + " then " + Output1.publicate() + " "
						+ andOrOut + " " + Output2.publicate() + andOrOut + " " +Output3.publicate();
			}else {
					outMessage = "If " + Input1.publicate() + " " + andOrIn + " " + Input2.publicate() + " " 
					+ andOrIn + " " + Input3.publicate() + " " + andOrIn + " " + Input4.publicate() + " " 
					+ andOrIn + " "	+ Input5.publicate() + " then " + Output1.publicate() + " "
					+ andOrOut + " " + Output2.publicate() + andOrOut + " " +Output3.publicate();
			}
			return outMessage;
		}
		
		//Evaluates and gives the output 1 MF value to the Output MF
		public double ruleHeight (double valuei1, double valuei2, double valuei3, double valuei4, double valuei5){
			double mFHeight;
			if((Input3 == null)||(Input4 == null)||(Input5 == null)){
				mFHeight = Math.min(Input1.activation(valuei1), 
					 		   			  Input2.activation(valuei2));				
			}else{
				mFHeight = Math.min(Input5.activation(valuei5),
				   				    Math.min(Math.min(Input1.activation(valuei1), 
								 		   			  Input2.activation(valuei2)), 
											 Math.min(Input3.activation(valuei3), 
												   	  Input4.activation(valuei4))));
			}
			return mFHeight;
		}
		
		public double getCenter1(){
			return Output1.mean;
		}
		
		public double getCenter2(){
			return Output2.mean;
		}
		
		public double getCenter3(){
			return Output3.mean;
		}
}
